package apportioner

import (
	sqlc "bp/db/sqlc"
	"bp/internal/util"
)


func (s *ApportionerComServiceImp) genUpsertOffApportionmentParamsPtrsOfOverall(
	offTransactionPtr *sqlc.OffTransaction,
	theMapOfOffTransactionDetail OffTrialItemToOffTransactionDetailMap,
	theMapOfOffDistribution OffCompareKeyToItemAmountFactorMap,
	offTrialPtrs []*sqlc.OffTrial,
	offTransactionDetailPtrs []*sqlc.OffTransactionDetail,
) (
	upsertOffApportionmentParamsPtrs []*sqlc.UpsertOffApportionmentParams) {

	apportionScene := string(sqlc.EmOffApportionSceneOrder)
	apportionTypeOverall := string(sqlc.EmOffApportionTypeOverall)
	offTransactionDetailPtrsOfTransaction := s.entityHub.OffTransactionService.FilterOffTransactionDetailPtrs(offTransactionDetailPtrs, func(otd *sqlc.OffTransactionDetail) bool {
		return otd.TransactionID == offTransactionPtr.ID
	})

	// 找出剩余金额最大的试交易项目
	offTransactionDetailPtrMaxRemainAmount := s.FindOffTransactionDetailByMaxRemainAmount(offTransactionDetailPtrsOfTransaction, theMapOfOffDistribution)
	offCompareKeyOfMaxItemAmount := s.ExtractOwnerOffTransactionDetailKey()(offTransactionDetailPtrMaxRemainAmount)
	s.slog.Infof("offCompareKeyOfMaxItemAmount=>%+v", offCompareKeyOfMaxItemAmount)

	// 理论上overall对于一个交易只有一条
	// 目前多品和单品优惠是互斥,可以用原价占比来分摊
	for _, offTrialPtr := range offTrialPtrs {
		
		// 先计算排除最大占比的那些试算项目
		var offExcludeMaxItemAmount int32
		for _, ptr := range offTransactionDetailPtrsOfTransaction {
			k := s.ExtractOwnerOffTransactionDetailKey()(ptr)
			if k != offCompareKeyOfMaxItemAmount {
				off := int32(util.Fix0(float64(offTrialPtr.Off) * float64(theMapOfOffDistribution[k]) / 1000))
				offExcludeMaxItemAmount += off
				upsertOffApportionmentParamsPtrs = append(upsertOffApportionmentParamsPtrs, &sqlc.UpsertOffApportionmentParams{
					BrandID:                offTransactionPtr.BrandID,
					OwnerType:              offTransactionPtr.OwnerType,
					OwnerID:                offTransactionPtr.OwnerID,
					MemberID:               offTransactionPtr.MemberID,
					TransactionID:          offTransactionPtr.ID,
					OutTransNo:             offTransactionPtr.OutTransNo,
					OutOrderNo:             offTransactionPtr.OutOrderNo,
					OutAfterSaleNo:         offTransactionPtr.OutAfterSaleNo,
					OutOrderDetailID:       ptr.OutOrderDetailID,
					OutOrderDetailCnt:      ptr.OutOrderDetailCnt,
					OutAfterSaleDetailID:   ptr.OutAfterSaleDetailID,
					OutAfterSaleDetailCnt:  ptr.OutAfterSaleDetailCnt,
					ItemID:                 ptr.ItemID,
					ItemSpecID:             ptr.ItemSpecID,
					ItemPrice:              ptr.ItemPrice,
					ApportionScene:         apportionScene,
					ApportionType:          apportionTypeOverall,
					OfferType:              offTrialPtr.OfferType,
					OfferItemType:          offTrialPtr.OfferItemType,
					OfferItemApportionInfo: offTrialPtr.OfferItemTrialInfo,
					Off:                    off,
					Cnt:                    ptr.OutOrderDetailCnt,
				})
			}	
		}

		// 再计算最大占比的交易明细,用总优惠减去也有的优惠
		offOfMaxItemAmount := offTrialPtr.Off - offExcludeMaxItemAmount
		upsertOffApportionmentParamsPtrs = append(upsertOffApportionmentParamsPtrs, &sqlc.UpsertOffApportionmentParams{
			BrandID:                offTransactionPtr.BrandID,
			OwnerType:              offTransactionPtr.OwnerType,
			OwnerID:                offTransactionPtr.OwnerID,
			MemberID:               offTransactionPtr.MemberID,
			TransactionID:          offTransactionPtr.ID,
			OutTransNo:             offTransactionPtr.OutTransNo,
			OutOrderNo:             offTransactionPtr.OutOrderNo,
			OutAfterSaleNo:         offTransactionPtr.OutAfterSaleNo,
			OutOrderDetailID:       offTransactionDetailPtrMaxRemainAmount.OutOrderDetailID,
			OutOrderDetailCnt:      offTransactionDetailPtrMaxRemainAmount.OutOrderDetailCnt,
			OutAfterSaleDetailID:   offTransactionDetailPtrMaxRemainAmount.OutAfterSaleDetailID,
			OutAfterSaleDetailCnt:  offTransactionDetailPtrMaxRemainAmount.OutAfterSaleDetailCnt,
			ItemID:                 offTransactionDetailPtrMaxRemainAmount.ItemID,
			ItemSpecID:             offTransactionDetailPtrMaxRemainAmount.ItemSpecID,
			ItemPrice:              offTransactionDetailPtrMaxRemainAmount.ItemPrice,
			ApportionScene:         apportionScene,
			ApportionType:          apportionTypeOverall,
			OfferType:              offTrialPtr.OfferType,
			OfferItemType:          offTrialPtr.OfferItemType,
			OfferItemApportionInfo: offTrialPtr.OfferItemTrialInfo,
			Off:                    offOfMaxItemAmount,
			Cnt:                    offTransactionDetailPtrMaxRemainAmount.OutOrderDetailCnt,
		})
	}

	return
}